/*
 *  Copyright 2019-2025 Zheng Jie
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *  http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 */
package me.zhengjie.controller.inventory;


import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import lombok.RequiredArgsConstructor;

import java.util.List;

import me.zhengjie.annotation.Log;
import me.zhengjie.dao.InventoryTaskDao;
import me.zhengjie.dao.StoreOutsideDao;
import me.zhengjie.dao.dto.InventoryTaskQueryCriteria;
import me.zhengjie.enums.InboundStatusEnum;
import me.zhengjie.server.InventoryTaskService;
import me.zhengjie.server.MaterialService;
import me.zhengjie.server.StoreOutsideService;
import me.zhengjie.utils.IpUtils;
import me.zhengjie.utils.PageResult;
import me.zhengjie.vo.Inventory.*;
import me.zhengjie.vo.Result;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import io.swagger.annotations.*;

import java.io.IOException;
import java.util.Objects;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import com.baomidou.mybatisplus.extension.plugins.pagination.Page;

/**
 * @author laoxu
 * @date 2025-06-26
 **/
@RestController
@RequiredArgsConstructor
@Api(tags = "InventoryController")
@RequestMapping("/api/inventoryTask")
public class InventoryTaskController {

    private static final Logger InventoryTaskLog = LoggerFactory.getLogger("inventory");

    private final InventoryTaskService inventoryTaskService;

    private final MaterialService materialService;

    private final StoreOutsideService storeOutsideService;

    @ApiOperation("导出数据")
    @GetMapping(value = "/download")
    @PreAuthorize("@el.check('inventoryTask:list')")
    public void exportInventoryTask(HttpServletResponse response, InventoryTaskQueryCriteria criteria) throws IOException {
        inventoryTaskService.download(inventoryTaskService.queryAll(criteria), response);
    }

    @GetMapping
    @ApiOperation("查询InventoryController")
    @PreAuthorize("@el.check('inventoryTask:list')")
    public ResponseEntity<PageResult<InventoryTaskDao>> queryInventoryTask(InventoryTaskQueryCriteria criteria) {
        Page<Object> page = new Page<>(criteria.getPage(), criteria.getSize());
        return new ResponseEntity<>(inventoryTaskService.queryAll(criteria, page), HttpStatus.OK);
    }

    @PostMapping
    @Log("新增InventoryController")
    @ApiOperation("新增InventoryController")
    @PreAuthorize("@el.check('inventoryTask:add')")
    public ResponseEntity<Object> createInventoryTask(@Validated @RequestBody InventoryTaskDao resources) {
        inventoryTaskService.create(resources);
        return new ResponseEntity<>(HttpStatus.CREATED);
    }

    @PutMapping
    @Log("修改InventoryController")
    @ApiOperation("修改InventoryController")
    @PreAuthorize("@el.check('inventoryTask:edit')")
    public ResponseEntity<Object> updateInventoryTask(@Validated @RequestBody InventoryTaskDao resources) {
        inventoryTaskService.update(resources);
        return new ResponseEntity<>(HttpStatus.NO_CONTENT);
    }

    @DeleteMapping
    @Log("删除InventoryController")
    @ApiOperation("删除InventoryController")
    @PreAuthorize("@el.check('inventoryTask:del')")
    public ResponseEntity<Object> deleteInventoryTask(@ApiParam(value = "传ID数组[]") @RequestBody List<String> ids) {
        inventoryTaskService.deleteAll(ids);
        return new ResponseEntity<>(HttpStatus.OK);
    }

    @RequestMapping(value = "findInventoryTaskData", method = RequestMethod.GET)
    @ResponseBody
    public ResponseEntity<PageResult<InventoryTaskDao>> findInventoryTaskData(@ModelAttribute InventoryTaskQueryCriteria criteria,HttpServletRequest request1) {
        InventoryTaskLog.info("查询盘点单信息");
        Page<InventoryTaskDao> inventoryTaskData = inventoryTaskService.findInventoryTaskData(criteria);
        PageResult<InventoryTaskDao> pageResult = new PageResult<>();
        pageResult.setContent(inventoryTaskData.getRecords());
        pageResult.setTotalElements(inventoryTaskData.getTotal());
        return new ResponseEntity<>(pageResult, HttpStatus.OK);
    }

    @RequestMapping(value = "findInventoryTaskDetails", method = RequestMethod.GET)
    @ResponseBody
    public ResponseEntity<PageResult<InventoryDetailsVo>> findInventoryTaskDetails(String taskId, Integer page, Integer size, String materialCode, String containerCode, Integer taskStatus) {
        InventoryTaskLog.info("查询盘点单详情信息");
        return new ResponseEntity<>(inventoryTaskService.findInventoryTaskDetails(taskId, page, size, materialCode, containerCode, taskStatus), HttpStatus.OK);
    }

    @RequestMapping(value = "findAvailableExtractData", method = RequestMethod.GET)
    @ResponseBody
    public ResponseEntity<PageResult<ContainerExtractVo>> findAvailableExtractData(@ModelAttribute InventoryExtractBaseVo inventoryExtractBaseVo) {
        InventoryTaskLog.info("抽盘盘点查询物料信息");
        Page<ContainerExtractVo> availableData = inventoryTaskService.findAvailableExtractData(inventoryExtractBaseVo);
        PageResult<ContainerExtractVo> pageResult = new PageResult<>();
        pageResult.setContent(availableData.getRecords());
        pageResult.setTotalElements(availableData.getTotal());
        return new ResponseEntity<>(pageResult, HttpStatus.OK);

    }

    @RequestMapping(value = "findAvailableMoveData", method = RequestMethod.GET)
    @ResponseBody
    public ResponseEntity<PageResult<ContainerMoveVo>> findAvailableMoveData(@ModelAttribute InventoryMoveBaseVo inventoryMoveBaseVo) {
        InventoryTaskLog.info("动碰盘点查询物料信息");
        Page<ContainerMoveVo> availableData = inventoryTaskService.findAvailableMoveData(inventoryMoveBaseVo);
        PageResult<ContainerMoveVo> pageResult = new PageResult<>();
        pageResult.setContent(availableData.getRecords());
        pageResult.setTotalElements(availableData.getTotal());
        return new ResponseEntity<>(pageResult, HttpStatus.OK);
    }

    @RequestMapping(value = "startInventoryTask", method = RequestMethod.GET)
    @ResponseBody
    public Result<?> startInventoryTask(String startName, String taskId) {
        InventoryTaskLog.info("开始盘点任务单");
        return inventoryTaskService.startInventoryTask(startName, taskId);
    }

    // @Scheduled(fixedDelay = 5000)
    public void outBoundInventoryTask() {
        InventoryTaskLog.info("出库盘点任务单");
        inventoryTaskService.outBoundInventoryTask();
    }

    @RequestMapping(value = "unbindRelationship", method = RequestMethod.GET)
    @ResponseBody
    public Result<?> unbindRelationship(String storeId) {
        InventoryTaskLog.info("抽检区储位解绑");
        // 修改库外储位状态, 设置载具编码
        StoreOutsideDao storeOutsideDao = new StoreOutsideDao()
                .setId(storeId)
                .setStatus(InboundStatusEnum.STORAGE_FREE.status);
        boolean result = storeOutsideService.updateData(storeOutsideDao);
        if (result) {
            return Result.success();
        } else {
            return Result.error();
        }
    }

    @RequestMapping(value = "inventoryScanContainer", method = RequestMethod.GET)
    @ResponseBody
    public Result<?> inventoryScanContainer(String containerCode) {
        InventoryTaskLog.info("盘点扫描载具码");
        return inventoryTaskService.inventoryScanContainer(containerCode);
    }

    @RequestMapping(value = "inventoryScanMaterial", method = RequestMethod.GET)
    @ResponseBody
    public Result<?> inventoryScanMaterial(String containerCode, String itemBarCode) {
        InventoryTaskLog.info("盘点扫描物料条码");
        if (containerCode == null || itemBarCode == null) {
            return Result.error("参数不能为空");
        }
        return inventoryTaskService.inventoryScanMaterial(containerCode, itemBarCode);
    }

    @RequestMapping(value = "inventoryUpdateQuantity", method = RequestMethod.GET)
    @ResponseBody
    public Result<?> inventoryUpdateQuantity(String itemBarCode, Double quantity) {
        InventoryTaskLog.info("盘点更新物料数量和重量");
        return inventoryTaskService.inventoryUpdateQuantity(itemBarCode, quantity);
    }

    @RequestMapping(value = "reportMissing", method = RequestMethod.GET)
    @ResponseBody
    public Result<?> reportMissing(String itemBarCode) {
        InventoryTaskLog.info("物料条码报缺记录");
        return inventoryTaskService.reportMissing(itemBarCode);
    }

    @RequestMapping(value = "inventoryCompleteMaterial", method = RequestMethod.GET)
    @ResponseBody
    public Result<?> inventoryCompleteMaterial(String containerCode) {
        InventoryTaskLog.info("盘点任务完成");
        return inventoryTaskService.inventoryCompleteMaterial(containerCode);
    }

}